<template>
  <div class="bg-white rounded-lg shadow">
    <!-- 表格头部 -->
    <div v-if="$slots.header || title" class="px-6 py-4 border-b border-gray-200">
      <slot name="header">
        <h3 class="text-lg font-medium text-gray-900">{{ title }}</h3>
      </slot>
    </div>

    <!-- 搜索和操作栏 -->
    <div v-if="$slots.toolbar" class="px-6 py-4 border-b border-gray-200">
      <slot name="toolbar"></slot>
    </div>

    <!-- 表格 -->
    <div class="overflow-x-auto">
      <table class="min-w-full divide-y divide-gray-200">
        <!-- 表头 -->
        <thead class="bg-gray-50">
          <tr>
            <!-- 选择列 -->
            <th v-if="selectable" class="px-6 py-3 text-left">
              <input
                type="checkbox"
                :checked="isAllSelected"
                @change="toggleSelectAll"
                class="h-4 w-4 text-primary focus:ring-primary border-gray-300 rounded"
              >
            </th>
            
            <!-- 数据列 -->
            <th
              v-for="column in columns"
              :key="column.key"
              :class="[
                'px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider',
                column.sortable ? 'cursor-pointer hover:bg-gray-100' : ''
              ]"
              @click="column.sortable && handleSort(column.key)"
            >
              <div class="flex items-center space-x-1">
                <span>{{ column.title }}</span>
                <div v-if="column.sortable" class="flex flex-col">
                  <ChevronUpIcon 
                    :class="[
                      'h-3 w-3',
                      sortKey === column.key && sortOrder === 'asc' 
                        ? 'text-primary' 
                        : 'text-gray-400'
                    ]"
                  />
                  <ChevronDownIcon 
                    :class="[
                      'h-3 w-3 -mt-1',
                      sortKey === column.key && sortOrder === 'desc' 
                        ? 'text-primary' 
                        : 'text-gray-400'
                    ]"
                  />
                </div>
              </div>
            </th>
            
            <!-- 操作列 -->
            <th v-if="$slots.actions" class="px-6 py-3 text-right text-xs font-medium text-gray-500 uppercase tracking-wider">
              操作
            </th>
          </tr>
        </thead>
        
        <!-- 表体 -->
        <tbody class="bg-white divide-y divide-gray-200">
          <tr 
            v-for="(item, index) in paginatedData" 
            :key="getRowKey(item, index)"
            :class="[
              'hover:bg-gray-50 transition-colors',
              selectedRows.includes(getRowKey(item, index)) ? 'bg-blue-50' : ''
            ]"
          >
            <!-- 选择列 -->
            <td v-if="selectable" class="px-6 py-4">
              <input
                type="checkbox"
                :checked="selectedRows.includes(getRowKey(item, index))"
                @change="toggleSelectRow(getRowKey(item, index))"
                class="h-4 w-4 text-primary focus:ring-primary border-gray-300 rounded"
              >
            </td>
            
            <!-- 数据列 -->
            <td 
              v-for="column in columns" 
              :key="column.key"
              class="px-6 py-4 whitespace-nowrap"
            >
              <slot 
                :name="`column-${column.key}`" 
                :item="item" 
                :value="getColumnValue(item, column.key)"
                :index="index"
              >
                <span :class="column.class || 'text-sm text-gray-900'">
                  {{ formatColumnValue(item, column) }}
                </span>
              </slot>
            </td>
            
            <!-- 操作列 -->
            <td v-if="$slots.actions" class="px-6 py-4 whitespace-nowrap text-right text-sm font-medium">
              <slot name="actions" :item="item" :index="index"></slot>
            </td>
          </tr>
          
          <!-- 空状态 -->
          <tr v-if="paginatedData.length === 0">
            <td :colspan="totalColumns" class="px-6 py-12 text-center">
              <slot name="empty">
                <div class="text-gray-500">
                  <svg class="mx-auto h-12 w-12 text-gray-400" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                    <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z" />
                  </svg>
                  <p class="mt-2 text-sm">暂无数据</p>
                </div>
              </slot>
            </td>
          </tr>
        </tbody>
      </table>
    </div>

    <!-- 分页 -->
    <div v-if="pagination && totalPages > 1" class="px-6 py-4 border-t border-gray-200">
      <div class="flex items-center justify-between">
        <div class="text-sm text-gray-700">
          显示第 {{ (currentPage - 1) * pageSize + 1 }} 到 {{ Math.min(currentPage * pageSize, filteredData.length) }} 条，
          共 {{ filteredData.length }} 条记录
        </div>
        
        <div class="flex items-center space-x-2">
          <button
            :disabled="currentPage === 1"
            @click="goToPage(currentPage - 1)"
            class="px-3 py-1 text-sm border border-gray-300 rounded hover:bg-gray-50 disabled:opacity-50 disabled:cursor-not-allowed"
          >
            上一页
          </button>
          
          <div class="flex space-x-1">
            <button
              v-for="page in visiblePages"
              :key="page"
              @click="goToPage(page)"
              :class="[
                'px-3 py-1 text-sm border rounded',
                page === currentPage
                  ? 'bg-primary text-white border-primary'
                  : 'border-gray-300 hover:bg-gray-50'
              ]"
            >
              {{ page }}
            </button>
          </div>
          
          <button
            :disabled="currentPage === totalPages"
            @click="goToPage(currentPage + 1)"
            class="px-3 py-1 text-sm border border-gray-300 rounded hover:bg-gray-50 disabled:opacity-50 disabled:cursor-not-allowed"
          >
            下一页
          </button>
        </div>
      </div>
    </div>
  </div>
</template>

<script setup>
import { ref, computed, watch } from 'vue'
import { ChevronUpIcon, ChevronDownIcon } from '@heroicons/vue/24/outline'

const props = defineProps({
  title: {
    type: String,
    default: ''
  },
  columns: {
    type: Array,
    required: true
  },
  data: {
    type: Array,
    default: () => []
  },
  rowKey: {
    type: [String, Function],
    default: 'id'
  },
  selectable: {
    type: Boolean,
    default: false
  },
  pagination: {
    type: Boolean,
    default: true
  },
  pageSize: {
    type: Number,
    default: 10
  },
  loading: {
    type: Boolean,
    default: false
  }
})

const emit = defineEmits(['sort', 'selection-change', 'page-change'])

// 排序
const sortKey = ref('')
const sortOrder = ref('asc')

// 分页
const currentPage = ref(1)

// 选择
const selectedRows = ref([])

// 排序数据
const sortedData = computed(() => {
  if (!sortKey.value) return props.data
  
  return [...props.data].sort((a, b) => {
    const aVal = getColumnValue(a, sortKey.value)
    const bVal = getColumnValue(b, sortKey.value)
    
    if (aVal < bVal) return sortOrder.value === 'asc' ? -1 : 1
    if (aVal > bVal) return sortOrder.value === 'asc' ? 1 : -1
    return 0
  })
})

// 过滤数据（可扩展）
const filteredData = computed(() => sortedData.value)

// 分页数据
const paginatedData = computed(() => {
  if (!props.pagination) return filteredData.value
  
  const start = (currentPage.value - 1) * props.pageSize
  const end = start + props.pageSize
  return filteredData.value.slice(start, end)
})

// 总页数
const totalPages = computed(() => {
  return Math.ceil(filteredData.value.length / props.pageSize)
})

// 可见页码
const visiblePages = computed(() => {
  const pages = []
  const total = totalPages.value
  const current = currentPage.value
  
  if (total <= 7) {
    for (let i = 1; i <= total; i++) {
      pages.push(i)
    }
  } else {
    if (current <= 4) {
      for (let i = 1; i <= 5; i++) {
        pages.push(i)
      }
      pages.push('...', total)
    } else if (current >= total - 3) {
      pages.push(1, '...')
      for (let i = total - 4; i <= total; i++) {
        pages.push(i)
      }
    } else {
      pages.push(1, '...')
      for (let i = current - 1; i <= current + 1; i++) {
        pages.push(i)
      }
      pages.push('...', total)
    }
  }
  
  return pages.filter(page => page !== '...' || pages.indexOf(page) === pages.lastIndexOf(page))
})

// 总列数
const totalColumns = computed(() => {
  let count = props.columns.length
  if (props.selectable) count++
  if (props.$slots?.actions) count++
  return count
})

// 是否全选
const isAllSelected = computed(() => {
  return paginatedData.value.length > 0 && 
         selectedRows.value.length === paginatedData.value.length &&
         paginatedData.value.every(item => selectedRows.value.includes(getRowKey(item)))
})

// 获取行键
const getRowKey = (item, index = 0) => {
  if (typeof props.rowKey === 'function') {
    return props.rowKey(item, index)
  }
  return item[props.rowKey] || index
}

// 获取列值
const getColumnValue = (item, key) => {
  return key.split('.').reduce((obj, k) => obj?.[k], item)
}

// 格式化列值
const formatColumnValue = (item, column) => {
  const value = getColumnValue(item, column.key)
  
  if (column.formatter && typeof column.formatter === 'function') {
    return column.formatter(value, item)
  }
  
  return value
}

// 处理排序
const handleSort = (key) => {
  if (sortKey.value === key) {
    sortOrder.value = sortOrder.value === 'asc' ? 'desc' : 'asc'
  } else {
    sortKey.value = key
    sortOrder.value = 'asc'
  }
  
  emit('sort', { key: sortKey.value, order: sortOrder.value })
}

// 切换全选
const toggleSelectAll = () => {
  if (isAllSelected.value) {
    selectedRows.value = []
  } else {
    selectedRows.value = paginatedData.value.map(item => getRowKey(item))
  }
  emit('selection-change', selectedRows.value)
}

// 切换行选择
const toggleSelectRow = (rowKey) => {
  const index = selectedRows.value.indexOf(rowKey)
  if (index > -1) {
    selectedRows.value.splice(index, 1)
  } else {
    selectedRows.value.push(rowKey)
  }
  emit('selection-change', selectedRows.value)
}

// 跳转页面
const goToPage = (page) => {
  if (page >= 1 && page <= totalPages.value) {
    currentPage.value = page
    emit('page-change', page)
  }
}

// 监听数据变化，重置页码
watch(() => props.data, () => {
  currentPage.value = 1
  selectedRows.value = []
})
</script>